package com.niit.controller;

import com.niit.entity.Admin;
import com.niit.entity.Info;
import com.niit.entity.LoginLog;
import com.niit.entity.User;
import com.niit.entity.dto.LoginAccountDTO;
import com.niit.service.AdminService;
import com.niit.service.InfoService;
import com.niit.service.LoginLogService;
import com.niit.service.UserService;
import com.niit.utils.Result;
import com.niit.utils.exception.SystemControllerException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.http.HttpStatus;
import org.springframework.web.bind.annotation.*;

import java.time.LocalDateTime;
import java.util.List;

@RestController
@RequestMapping("/api/account")
public class AccountController {

	@Autowired
	private AdminService adminService;
	@Autowired
	private UserService userService;
	@Autowired
	private InfoService infoService;
	@Autowired
	private LoginLogService loginLogService;

	@PostMapping("/login")
	public LoginAccountDTO login(
			@RequestParam String phone,
			@RequestParam String password,
			@RequestParam(required = false, defaultValue = "1") Integer loginType
	) {
		try {
			//判断账号存在
			Info info = infoService.findByPhone(phone);
			if(info == null || !info.getPassword().equals(password)) {
				return new LoginAccountDTO(HttpStatus.FORBIDDEN.value(), "账号或密码错误");
			}

			Object account = switch (loginType) {
				case 1 -> userService.findByInfoIdAndUserType(info.getId(), false);
				case 2 -> userService.findByInfoIdAndUserType(info.getId(), true);
				case 3 -> adminService.findByInfoId(info.getId());
				default -> null;
			};
			if(account == null) {
				return new LoginAccountDTO(HttpStatus.FORBIDDEN.value(), "不存在该用户");
			}
			LoginAccountDTO sessionAccount = new LoginAccountDTO();
			if(loginType != 3){
				LoginLog loginLog = new LoginLog();
				loginLog.setLoginType(true);
				loginLog.setUser((User) account);
				loginLogService.save(loginLog);
				sessionAccount.setUser((User) account);
			}else{
				sessionAccount.setAdmin((Admin) account);
			}
			sessionAccount.setStatus(HttpStatus.OK.value());
			sessionAccount.setMsg(info.getUsername());
			return sessionAccount;
		}catch (Exception e) {
			throw new SystemControllerException("内部服务器出错\n" + e.getMessage());
		}
	}

	/**
	 * @param phone 手机号
	 * @param password 密码
	 * @param registerType 登录类型 1-求职者 2-招聘者 3-管理员
	 * @return Result<Object>
	 */
	@PostMapping("/register")
	public Result<Object> register(
			@RequestParam String phone,
			@RequestParam String password,
			@RequestParam(required = false, defaultValue = "1") Integer registerType
	){
		try {
			Result<Object> forbidden = Result.success(HttpStatus.FORBIDDEN.value());
			Result<Object> ok = Result.success(HttpStatus.OK.value());
			Info newinfo = new Info();
			Info info = infoService.findByPhone(phone);
			Object existAccount;

			//info == null - 数据库无信息，新账户
			boolean isNewAccount = info == null;
			if(isNewAccount){
				newinfo.setUsername(phone);
				newinfo.setPhone(phone);
				newinfo.setPassword(password);
				newinfo.setCreateTime(LocalDateTime.now());
				newinfo = infoService.save(newinfo);
			}else {
				//获取对应注册类型对应的account数据，如果存在表示该手机号的账户是有这个角色的
				if(!password.equals(info.getPassword())) return forbidden.msg("账号已存在");
				existAccount = switch (registerType) {
					case 1 -> userService.findByInfoIdAndUserType(info.getId(), false);
					case 2 -> userService.findByInfoIdAndUserType(info.getId(), true);
					case 3 -> adminService.findByInfoId(info.getId());
					default -> null;
				};
				if(existAccount != null && password.equals(info.getPassword())) {
					return forbidden.msg("该手机号已被注册！若注册不同身份请输入正确密码且勾选未注册过的身份！");
				}
			}

			// 新账号/旧账号新角色 共用一段代码注册
			info = isNewAccount ? newinfo : info;
			User newuser = new User();
			newuser.setInfo(info);
			Object account = switch (registerType){
				case 1 -> {
					newuser.setUserType(false);
					yield userService.save(newuser);
				}
				case 2 -> {
					newuser.setUserType(true);
					yield userService.save(newuser);
				}
				case 3 -> {
					Admin admin = new Admin();
					admin.setInfo(newinfo);
					yield adminService.save(admin);
				}
				default -> null;
			};

			//判断注册成功与否
			if(account == null) return forbidden.msg("注册失败！错误参数类型");
			//根据注册类型返回相应结果
			if(isNewAccount) return ok.msg("注册成功~请重新登录~");
			else return ok.msg("检测到该手机号已注册过其他角色，已自动绑定");
		}catch (Exception e) {
			throw new SystemControllerException("内部服务器出错\n" + e.getMessage());
		}
	}

	@PostMapping("/logout")
	public Result<Object> logout(@RequestBody LoginAccountDTO loginAccountDTO) {
		try{
			if(loginAccountDTO.getUser() != null){
				LoginLog loginLog = new LoginLog();
				loginLog.setLoginType(false);
				loginLog.setUser(loginAccountDTO.getUser());
				loginLogService.save(loginLog);
			}
			return Result.success(HttpStatus.OK.value());
		}catch (Exception e) {
			throw new SystemControllerException("内部服务器出错\n" + e.getMessage());
		}
	}

	@PostMapping("/updateUser")
	public User updateUser(@RequestBody User user){
		return userService.save(user);
	}

	@PostMapping("/getAllUser")
	public Page<User> getAllUser(
			@RequestParam(required = false) String phone,
			@RequestParam(required = false) String username,
			@RequestParam(required = false) String realName,
			@RequestParam(required = false) String gender,
			@RequestParam(required = false) Boolean userType,
			@RequestParam(defaultValue = "1") int page,
			@RequestParam(defaultValue = "10") int size
	){
		PageRequest pageRequest = PageRequest.of(page - 1, size);
		return userService.findAll(phone, username, realName, gender, userType, pageRequest);
	}

	@PostMapping("/getUser/{id}")
	User getUser(@PathVariable Integer id){
		return userService.findById(id);
	}

	@PostMapping("/getAdmin/{id}")
	Admin getAdmin(@PathVariable Integer id){
		return adminService.findById(id);
	}

	@PostMapping("/deleteUser")
	void deleteUserById(@RequestParam Integer id){
		userService.deleteById(id);
	}
}
